To be able to edit code and run cells, you need to run the notebook yourself. Where would you like to run the notebook?

In the cloud (experimental)

Binder is a free, open source service that runs scientific notebooks in the cloud! It will take a while, usually 2-7 minutes to get a session.

On your computer

(Recommended if you want to store your changes.)

  1. Copy the notebook URL:
  2. Run Pluto

    (Also see: How to install Julia and Pluto)

  3. Paste URL in the Open box

Frontmatter

If you are publishing this notebook on the web, you can set the parameters below to provide HTML metadata. This is useful for search engines and social media.

Author 1

Lecture 23: Solving Partial Differential Equations (PDEs) Numerically

Part II: Heat transport by ocean currents (two-dimensional advection and diffusion)

👀 Reading hidden code
8.4 ms
👀 Reading hidden code
124 μs

1) Background: two-dimensional advection-diffusion

1.1) The two-dimensional advection-diffusion equation

Recall from Lecture 22 that the one-dimensional advection-diffusion equation is written as

T(x,t)t=UTx+κ2Tx2,

where T(x,t) is the temperature, U is a constant advective velocity and κ is the diffusivity.

The two-dimensional advection diffusion equation simply adds advection and diffusion operators acting in a second dimensions y (orthogonal to x).

T(x,y,t)t=u(x,y)Tx+v(x,y)Ty+κ(2Tx2+2Ty2),

where u(x,y)=(u,v)=ux^+vy^ is a velocity vector field.

Throughout the rest of the Climate Modelling module, we will consider x to be the longitundinal direction (positive from west to east) and y to the be the latitudinal direction (positive from south to north).

👀 Reading hidden code
21.3 ms
1.2) Multivariable shorthand notation

Conventionally, the two-dimensional advection-diffusion equation is written more succintly as

T(x,y,t)t=uT+κ2T,

using the following shorthand notation.

The gradient operator is defined as

(x,y)

such that

T=(Tx,Ty)

and

uT=(u,v)(Tx,Ty)=uTx+vTy.

The Laplacian operator 2 (sometimes denoted Δ) is defined as

2=2x2+2y2

such that

2T=2Tx2+2Ty2.

The divergence operator is defined as [], such that

u=(x,x)(u,v)=ux+vy.

Note: Since seawater is largely incompressible, we can approximate ocean currents as a non-divergent flow, with u=ux+vy=0. Among other implications, this allows us to write:

\begin{align} \vec{u} \cdot \nabla T&= u\frac{\partial T(x,y,t)}{\partial x} + v\frac{\partial T(x,y,t)}{\partial y}\newline &= u\frac{\partial T}{\partial x} + v\frac{\partial T}{\partial y} + T\left(\frac{\partial u}{\partial x} + \frac{\partial v}{\partial y}\right)\newline &= \left( u\frac{\partial T}{\partial x} + T\frac{\partial u}{\partial x} \right) + \left( v\frac{\partial T}{\partial y} + \frac{\partial v}{\partial y} \right) \newline &= \frac{\partial (uT)}{\partial x} + \frac{\partial (vT)}{\partial x}\newline &= \nabla \cdot (\vec{u}T) \end{align}

using the product rule (separately in both x and y).

👀 Reading hidden code
14.8 ms
1.3) The flux-form two-dimensional advection-diffusion equation

This lets us finally re-write the two-dimensional advection-diffusion equation as:

Tt=(uT)+κ2T

which is the form we will use in our numerical algorithm below.

👀 Reading hidden code
329 μs

2)

md"""
### 2)
"""
👀 Reading hidden code
179 μs
begin
Δx = 0.04
Δy = 0.04
xs = (0. -Δx/2.:Δx:1. +Δx/2.)'
ys = (-1. -Δy/2.:Δy:1. +Δx/2.)
Nx = length(xs)
Ny = length(ys)
end;
👀 Reading hidden code
54.2 μs
size(T)
👀 Reading hidden code
12.3 μs
0.005
Δt = 0.005
👀 Reading hidden code
10.3 μs
3×3 OffsetArray(::Matrix{Float64}, -1:1, -1:1) with eltype Float64 with indices -1:1×-1:1:
 0.0   1.0  0.0
 1.0  -4.0  1.0
 0.0   1.0  0.0
begin
diff_kernel = OffsetArray(zeros(Float64, 3,3), -1:1, -1:1)
diff_kernel[0, 0] = -4
diff_kernel[-1, 0] = 1.; diff_kernel[1, 0] = 1.;
diff_kernel[0, -1] = 1.; diff_kernel[0, 1] = 1.;
diff_kernel
end
👀 Reading hidden code
54.1 ms
plot_kernel(diff_kernel)
👀 Reading hidden code
5.4 s
diffuse (generic function with 2 methods)
begin
function diffuse(T, j, i)
return κ.*sum(diff_kernel[-1:1,-1:1].*T[j-1:j+1, i-1:i+1])/(2Δx^2)
end
diffuse(T) = [diffuse(T, j, i) for j=2:Ny-1, i=2:Nx-1]
end
👀 Reading hidden code
1.8 ms
3×3 OffsetArray(::Matrix{Float64}, -1:1, -1:1) with eltype Float64 with indices -1:1×-1:1:
  0.0  -1.0  0.0
 -1.0   0.0  1.0
  0.0   1.0  0.0
begin
adv_kernel = OffsetArray(zeros(Float64, 3,3), -1:1, -1:1)
adv_kernel[-1, 0] = -1.; adv_kernel[1, 0] = 1.;
adv_kernel[0, -1] = -1.; adv_kernel[0, 1] = 1.;
adv_kernel
end
👀 Reading hidden code
53.6 μs
plot_kernel(adv_kernel)
👀 Reading hidden code
1.7 ms
1×27 adjoint(::StepRangeLen{Float64, Base.TwicePrecision{Float64}, Base.TwicePrecision{Float64}, Int64}) with eltype Float64:
 -0.02  0.02  0.06  0.1  0.14  0.18  0.22  …  0.78  0.82  0.86  0.9  0.94  0.98  1.02
xs
👀 Reading hidden code
9.3 μs
plot_kernel (generic function with 1 method)
plot_kernel(A) = heatmap(
collect(A),
color=:bluesreds, clims=(-maximum(abs.(A)), maximum(abs.(A))), colorbar=false,
xticks=false, yticks=false, size=(100, 100), xaxis=false, yaxis=false
)
👀 Reading hidden code
828 μs
advect (generic function with 2 methods)
begin
function advect(T, j, i)
return .-(
sum(adv_kernel[0, -1:1].*(U[j, i-1:i+1].*T[j, i-1:i+1]))/(2Δx) .+
sum(adv_kernel[-1:1, 0].*(V[j-1:j+1, i].*T[j-1:j+1, i]))/(2Δy)
)
end
advect(T) = [advect(T, j, i) for j=2:Ny-1, i=2:Nx-1]
end
👀 Reading hidden code
2.2 ms
update_ghostcells! (generic function with 1 method)
function update_ghostcells!(A; option="no-flux")
Atmp = @view A[:,:]
if option=="no-flux"
A[1, :] = Atmp[2, :]; Atmp[end, :] = Atmp[end-1, :]
A[:, 1] = Atmp[:, 2]; Atmp[:, end] = Atmp[:, end-1]
end
end
👀 Reading hidden code
13.7 ms
50×25 Matrix{Float64}:
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  …  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0     -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0     -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0     -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0     -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  …  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0     -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
  ⋮                             ⋮          ⋱         ⋮                      
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0     -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  …  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0     -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0     -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0     -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
 -0.0  -0.0  -0.0  -0.0  -0.0  -0.0  -0.0     -0.0  -0.0  -0.0  -0.0  -0.0  -0.0
advect(T)
👀 Reading hidden code
375 ms
50×25 Matrix{Float64}:
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0  …  0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0     0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0     0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0     0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0     0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0  …  0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0     0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
 ⋮                        ⋮              ⋱                 ⋮                   
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0     0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0  …  0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0     0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0     0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0     0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
 0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0     0.0  0.0  0.0  0.0  0.0  0.0  0.0  0.0
diffuse(T)
👀 Reading hidden code
276 ms
outgoing_thermal_radiation (generic function with 1 method)
function outgoing_thermal_radiation(T)
A .- B .* (T .- T0)
end
👀 Reading hidden code
452 μs
plot(-20:20, α, ylim=(0,1))
👀 Reading hidden code
478 ms
α (generic function with 1 method)
function α(T; α0=α0, αi=αi, ΔT=3.)
if T < -ΔT
return αi
elseif -ΔT <= T < ΔT
return αi + (α0-αi)*(T+ΔT)/(2ΔT)
elseif T >= ΔT
return α0
end
end
👀 Reading hidden code
2.1 ms
52×27 Matrix{Float64}:
 45.4957   45.4957   45.4957   45.4957   …  45.4957   45.4957   45.4957   45.4957
 45.4957   45.4957   45.4957   45.4957      45.4957   45.4957   45.4957   45.4957
 45.4611   45.4611   45.4611   45.4611      45.4611   45.4611   45.4611   45.4611
 45.3921   45.3921   45.3921   45.3921      45.3921   45.3921   45.3921   45.3921
 45.2886   45.2886   45.2886   45.2886      45.2886   45.2886   45.2886   45.2886
 45.1508   45.1508   45.1508   45.1508   …  45.1508   45.1508   45.1508   45.1508
 44.9788   44.9788   44.9788   44.9788      44.9788   44.9788   44.9788   44.9788
  ⋮                                      ⋱                       ⋮        
 15.4315   15.4315   15.4315   15.4315      15.4315   15.4315   15.4315   15.4315
 14.3407   14.3407   14.3407   14.3407      14.3407   14.3407   14.3407   14.3407
 13.2461   13.2461   13.2461   13.2461      13.2461   13.2461   13.2461   13.2461
 12.1487   12.1487   12.1487   12.1487      12.1487   12.1487   12.1487   12.1487
 11.0498   11.0498   11.0498   11.0498   …  11.0498   11.0498   11.0498   11.0498
  9.95024   9.95024   9.95024   9.95024      9.95024   9.95024   9.95024   9.95024
Ss = [
S_peak .* (cos((y+1) * π/4) + .3)
for y in ys, x in xs[:]
]
👀 Reading hidden code
56.6 μs
Error message

UndefVarError: S not defined

Stack trace

Here is what happened, the most recent locations are first:

  1. heatmap(S) |> as_png
heatmap(S) |> as_png
👀 Reading hidden code
---
absorbed_solar_radiation (generic function with 1 method)
function absorbed_solar_radiation(T)
absorption = 1.0 .- α.(T)
absorption .* Ss
end
👀 Reading hidden code
546 μs
begin
# Initial conditions
T = [
T0
for y in ys, x in xs[:]
]
t = Ref(0.)
end;
👀 Reading hidden code
52.7 μs
0.0
T0 = 0.0
👀 Reading hidden code
10.9 μs
begin
CFL_adv = maximum(V)*Δt/Δx
CFL_diff = κ*Δt/(Δx^2)
CFL_adv, CFL_diff
end
👀 Reading hidden code
51.2 μs
for i in 1:10
timestep!(t, T)
end
👀 Reading hidden code
288 ms
for i in 1:10
timestep2!(t, T)
end
👀 Reading hidden code
472 ms
function timestep2!(t, T)
update_ghostcells!(T)
T[2:end-1, 2:end-1] .+= Δt.*(
advect(T) .+ diffuse(T) .+
(absorbed_solar_radiation(T)[2:end-1, 2:end-1]) .-
(outgoing_thermal_radiation(T)[2:end-1, 2:end-1])
)
t[] += Δt
end;
👀 Reading hidden code
1.3 ms

Two-dimensional advection and diffusion

👀 Reading hidden code
184 μs
Need boundary conditions still!
👀 Reading hidden code
27.9 ms
plot(
-10:40, outgoing_thermal_radiation(-10:40),
xlabel="Temperature",
ylabel="Outgoing radiation"
)
👀 Reading hidden code
213 ms
function timestep!(t, T)
update_ghostcells!(T)
T[2:end-1, 2:end-1] .+= Δt*(
advect(T) .+ diffuse(T) .+
(@view absorbed_solar_radiation(T)[2:end-1, 2:end-1]) .-
(@view outgoing_thermal_radiation(T)[2:end-1, 2:end-1])
)
t[] += Δt
end;
👀 Reading hidden code
1.5 ms
image/svg+xml image/svg+xml image/svg+xml speed:
@bind go Clock(.1)
👀 Reading hidden code
235 ms

Increase global temperature by °C    

Set global temperature to °C    

👀 Reading hidden code
45.4 ms
begin
go
temperature_control_event_handled
nT = 50
for i = 1:nT
timestep!(t, T)
end
plot_state()
end
👀 Reading hidden code
1.8 s
0.0
go; mean(T)
👀 Reading hidden code
14.1 μs
0.015
κ = 0.015
👀 Reading hidden code
14.3 μs
0.3
α0=0.3
👀 Reading hidden code
11.4 μs
0.5
αi=0.5
👀 Reading hidden code
10.1 μs
11
A = 11
👀 Reading hidden code
11.2 μs
-0.7
B = -0.7
👀 Reading hidden code
11.0 μs
35.0
S_peak = 35.0
👀 Reading hidden code
14.9 μs
mean (generic function with 1 method)
mean(x) = sum(x) / length(x)
👀 Reading hidden code
405 μs
plot_state (generic function with 1 method)
function plot_state()
X = repeat(xitp(xs), size(yitp(ys),1), 1)
Y = repeat(yitp(ys), 1, size(xitp(xs),2))
p = temperature_heatmap(T)
Nq = 4
quiver!(p, X[(Nq+1)÷2:Nq:end], Y[(Nq+1)÷2:Nq:end], quiver=(U[(Nq+1)÷2:Nq:end]./10., V[(Nq+1)÷2:Nq:end]./10.), color=:black, alpha=0.7)
plot!(p, xlims=(0., 1.), ylims=(-1.0, 1.0))
plot!(p, xlabel="longitudinal distance", ylabel="latitudinal distance")
plot!(p, clabel="Temperature")
as_png(p)
end
👀 Reading hidden code
1.9 ms
Temperature control logic
begin
if !ismissing(temperature_control_event)
e = temperature_control_event
if e["type"] == "add"
T .+= e["value"]
elseif e["type"] == "set"
T .= e["value"]
end
end
temperature_control_event_handled = true
Text("Temperature control logic")
end
👀 Reading hidden code
49.7 μs
heatmap(xs', ys, ψ̂)
👀 Reading hidden code
362 ms

👀 Reading hidden code
82.2 μs
temperature_heatmap (generic function with 1 method)
function temperature_heatmap(T)
levels = -10:1.0:40
p = contourf(xs', ys, T,
levels=levels,
color=:bluesreds, colorbar_title="Temperature [°C]",
lw=0,
clims=extrema(levels)
)
contour!(p, xs', ys, T,
levels=[0],
color=:white,
lw=3
)
end
👀 Reading hidden code
925 μs
Setting up the velocity field
👀 Reading hidden code
187 μs
begin
ϵ = 0.05
xψ = (-Δx:Δx:1. +Δx)'
yψ = (-1-Δy:Δy:1. +Δy)
# See page 595 of Vallis Edt.2
ψ̂(x,y) = π*sin.(π*y) * (
1 .- x - exp.(-x/(2*ϵ)) .* (
cos.(√3*x/(2*ϵ)) .+
(1. /√3)*sin.(√3*x/(2*ϵ))
)
.+ ϵ*exp.((x .- 1.)/ϵ)
)
u,v = diagnose_velocities(ψ̂(xψ, yψ))
U = xitp(u) ./10.
V = yitp(v) ./10.
U[1,:] .= 0.; V[1,:] .= 0.;
U[end,:] .= 0.; V[end,:] .= 0.;
U[:,1] .= 0.; V[:,1] .= 0.;
U[:,end] .= 0.; V[:,end] .= 0.;
end;
👀 Reading hidden code
1.4 s
diagnose_velocities (generic function with 1 method)
begin
∂x(ϕ) = (ϕ[:,2:end] - ϕ[:,1:end-1])/Δx
∂y(ϕ) = (ϕ[2:end,:] - ϕ[1:end-1,:])/Δy
xpad(ϕ) = hcat(zeros(size(ϕ,1)), ϕ, zeros(size(ϕ,1)))
ypad(ϕ) = vcat(zeros(size(ϕ,2))', ϕ, zeros(size(ϕ,2))')
xitp(ϕ) = 0.5*(ϕ[:,2:end]+ϕ[:,1:end-1])
yitp(ϕ) = 0.5*(ϕ[2:end,:]+ϕ[1:end-1,:])
function diagnose_velocities(ψ)
u = ∂y(ψ)
v = -∂x(ψ)
return u,v
end
end
👀 Reading hidden code
2.8 ms
begin
import Pkg
Pkg.activate(mktempdir())
Pkg.add([
"Plots",
"PlutoUI",
"Images",
"FileIO",
"ImageMagick",
"ImageIO",
"OffsetArrays",
"ThreadsX",
"Strided",
])
using Plots
using PlutoUI
using Images
using OffsetArrays
using ThreadsX
using Strided
end
👀 Reading hidden code
❔
  Activating new project at `/tmp/jl_tbPDGm`
    Updating registry at `~/.julia/registries/General.toml`
   Resolving package versions...
   Installed CUDA_Driver_jll ──────── v0.5.0+1
   Installed CUDA_Runtime_Discovery ─ v0.2.4
   Installed BFloat16s ────────────── v0.4.2
   Installed CUDA_Runtime_jll ─────── v0.6.0+0
   Installed TupleTools ───────────── v1.6.0
   Installed RandomNumbers ────────── v1.6.0
   Installed GPUArrays ────────────── v8.8.1
   Installed LLVM ─────────────────── v6.1.0
   Installed EnzymeCore ───────────── v0.7.8
   Installed StridedViews ─────────── v0.3.2
   Installed Strided ──────────────── v2.2.0
   Installed KernelAbstractions ───── v0.9.34
   Installed PackageExtensionCompat ─ v1.0.2
   Installed Random123 ────────────── v1.6.2
   Installed UnsafeAtomicsLLVM ────── v0.1.5
   Installed Atomix ───────────────── v0.1.0
   Installed UnsafeAtomics ────────── v0.2.1
   Installed LLVMExtra_jll ────────── v0.0.23+0
   Installed GPUCompiler ──────────── v0.21.4
   Installed CUDA ─────────────────── v4.4.2
    Updating `/tmp/jl_tbPDGm/Project.toml`
  [5789e2e9] + FileIO v1.17.0
  [82e4d734] + ImageIO v0.6.9
  [6218d12a] + ImageMagick v1.4.0
  [916415d5] + Images v0.26.2
  [6fe1bfb0] + OffsetArrays v1.15.0
  [91a5bcdd] + Plots v1.40.7
  [7f904dfe] + PlutoUI v0.7.61
  [5e0ebb24] + Strided v2.2.0
  [ac1d9e8a] + ThreadsX v0.1.12
    Updating `/tmp/jl_tbPDGm/Manifest.toml`
  [621f4979] + AbstractFFTs v1.5.0
  [6e696c72] + AbstractPlutoDingetjes v1.3.2
  [7d9f7c33] + Accessors v0.1.41
  [79e6a3ab] + Adapt v3.7.2
  [66dad0bd] + AliasTables v1.1.3
  [dce04be8] + ArgCheck v2.4.0
  [ec485272] + ArnoldiMethod v0.4.0
  [4fba245c] + ArrayInterface v7.5.1
  [a9b6321e] + Atomix v0.1.0
  [13072b0f] + AxisAlgorithms v1.1.0
  [39de3d68] + AxisArrays v0.4.7
  [ab4f0b2a] + BFloat16s v0.4.2
  [198e06fe] + BangBang v0.4.3
  [9718e550] + Baselet v0.1.1
  [d1d4a3ce] + BitFlags v0.1.9
  [62783981] + BitTwiddlingConvenienceFunctions v0.1.6
  [fa961155] + CEnum v0.4.2
  [2a0fbf3d] + CPUSummary v0.2.6
  [052768ef] + CUDA v4.4.2
  [1af6417a] + CUDA_Runtime_Discovery v0.2.4
  [aafaddc9] + CatIndices v0.2.2
  [d360d2e6] + ChainRulesCore v1.25.1
  [9e997f8a] + ChangesOfVariables v0.1.9
  [fb6a15b2] + CloseOpenIntervals v0.1.13
  [aaaa29a8] + Clustering v0.15.8
  [944b1d66] + CodecZlib v0.7.8
  [35d6a980] + ColorSchemes v3.29.0
  [3da002f7] + ColorTypes v0.11.5
  [c3611d14] + ColorVectorSpace v0.10.0
  [5ae59095] + Colors v0.13.0
  [bbf7d656] + CommonSubexpressions v0.3.1
  [34da2185] + Compat v4.16.0
  [a33af91c] + CompositionsBase v0.1.2
  [ed09eef8] + ComputationalResources v0.3.2
  [f0e56b4a] + ConcurrentUtilities v2.5.0
  [187b0558] + ConstructionBase v1.5.8
  [d38c429a] + Contour v0.6.3
  [150eb455] + CoordinateTransformations v0.6.3
  [adafc99b] + CpuId v0.3.1
  [dc8bdbbb] + CustomUnitRanges v1.0.2
  [9a962f9c] + DataAPI v1.16.0
  [864edb3b] + DataStructures v0.18.20
  [e2d170a0] + DataValueInterfaces v1.0.0
  [244e2a9f] + DefineSingletons v0.1.2
  [163ba53b] + DiffResults v1.1.0
  [b552c78f] + DiffRules v1.15.1
  [b4f34e82] + Distances v0.10.12
  [ffbed154] + DocStringExtensions v0.9.3
  [f151be2c] + EnzymeCore v0.7.8
  [460bff9d] + ExceptionUnwrapping v0.1.11
  [e2ba6199] + ExprTools v0.1.10
  [c87230d0] + FFMPEG v0.4.2
  [4f61f5a4] + FFTViews v0.3.2
  [7a1cc6ca] + FFTW v1.8.1
  [5789e2e9] + FileIO v1.17.0
  [53c48c17] + FixedPointNumbers v0.8.5
  [1fa38f19] + Format v1.3.7
  [f6369f11] + ForwardDiff v0.10.38
  [0c68f7d7] + GPUArrays v8.8.1
  [46192b85] + GPUArraysCore v0.1.5
  [61eb1bfa] + GPUCompiler v0.21.4
  [28b8d3ca] + GR v0.72.8
  [a2bd30eb] + Graphics v1.1.3
  [86223c79] + Graphs v1.12.0
  [42e2da0e] + Grisu v1.0.2
  [cd3eb016] + HTTP v1.10.15
  [2c695a8d] + HistogramThresholding v0.3.1
  [3e5b6fbb] + HostCPUFeatures v0.1.17
  [47d2ed2b] + Hyperscript v0.0.5
  [ac1192a8] + HypertextLiteral v0.9.5
  [b5f81e59] + IOCapture v0.2.5
  [615f187c] + IfElse v0.1.1
  [2803e5a7] + ImageAxes v0.6.12
  [c817782e] + ImageBase v0.1.7
  [cbc4b850] + ImageBinarization v0.3.1
  [f332f351] + ImageContrastAdjustment v0.3.12
  [a09fc81d] + ImageCore v0.10.5
  [89d5987c] + ImageCorners v0.1.3
  [51556ac3] + ImageDistances v0.2.17
  [6a3955dd] + ImageFiltering v0.7.9
  [82e4d734] + ImageIO v0.6.9
  [6218d12a] + ImageMagick v1.4.0
  [bc367c6b] + ImageMetadata v0.9.10
  [787d08f9] + ImageMorphology v0.4.5
  [2996bd0c] + ImageQualityIndexes v0.3.7
  [80713f31] + ImageSegmentation v1.8.4
  [4e3cecfd] + ImageShow v0.3.8
  [02fcd773] + ImageTransformations v0.10.1
  [916415d5] + Images v0.26.2
  [9b13fd28] + IndirectArrays v1.0.0
  [d25df0c9] + Inflate v0.1.5
  [22cec73e] + InitialValues v0.3.1
  [1d092043] + IntegralArrays v0.1.6
  [a98d9a8b] + Interpolations v0.15.1
  [8197267c] + IntervalSets v0.7.10
  [3587e190] + InverseFunctions v0.1.17
  [92d709cd] + IrrationalConstants v0.2.4
  [c8e1da08] + IterTools v1.4.0
  [82899510] + IteratorInterfaceExtensions v1.0.0
  [033835bb] + JLD2 v0.5.11
  [1019f520] + JLFzf v0.1.9
  [692b3bcd] + JLLWrappers v1.7.0
  [682c06a0] + JSON v0.21.4
  [b835a17e] + JpegTurbo v0.1.5
  [63c18a36] + KernelAbstractions v0.9.34
  [929cbde3] + LLVM v6.1.0
  [b964fa9f] + LaTeXStrings v1.4.0
  [23fbe1c1] + Latexify v0.16.6
  [10f19ff3] + LayoutPointers v0.1.17
  [8cdb02fc] + LazyModules v0.3.1
  [2ab3a3ac] + LogExpFunctions v0.3.28
  [e6f89c97] + LoggingExtras v1.1.0
  [bdcacae8] + LoopVectorization v0.12.171
  [6c6e2e6c] + MIMEs v1.0.0
  [1914dd2f] + MacroTools v0.5.15
  [d125e4d3] + ManualMemory v0.1.8
  [dbb5928d] + MappedArrays v0.4.2
  [739be429] + MbedTLS v1.1.9
  [442fdcdd] + Measures v0.3.2
  [626554b9] + MetaGraphs v0.8.0
  [128add7d] + MicroCollections v0.2.0
  [e1d29d7a] + Missings v1.2.0
  [e94cdb99] + MosaicViews v0.3.4
  [77ba4419] + NaNMath v1.0.3
  [b8a86587] + NearestNeighbors v0.4.21
  [f09324ee] + Netpbm v1.1.1
  [6fe1bfb0] + OffsetArrays v1.15.0
  [52e1d378] + OpenEXR v0.3.3
  [4d8831e6] + OpenSSL v1.4.3
  [bac558e1] + OrderedCollections v1.8.0
  [f57f5aa1] + PNGFiles v0.4.4
  [65ce6f38] + PackageExtensionCompat v1.0.2
  [5432bcbf] + PaddedViews v0.5.12
  [d96e819e] + Parameters v0.12.3
  [69de0a69] + Parsers v2.8.1
  [b98c9c47] + Pipe v1.3.0
  [eebad327] + PkgVersion v0.3.3
  [ccf2f8ad] + PlotThemes v3.3.0
  [995b91a9] + PlotUtils v1.4.3
  [91a5bcdd] + Plots v1.40.7
  [7f904dfe] + PlutoUI v0.7.61
  [1d0040c9] + PolyesterWeave v0.2.2
  [f27b6e38] + Polynomials v4.0.19
  [aea7be01] + PrecompileTools v1.2.1
  [21216c6a] + Preferences v1.4.3
  [92933f4c] + ProgressMeter v1.10.2
  [43287f4e] + PtrArrays v1.3.0
  [4b34888f] + QOI v1.0.1
  [94ee1d12] + Quaternions v0.7.6
  [74087812] + Random123 v1.6.2
  [e6cf234a] + RandomNumbers v1.6.0
  [b3c3ace0] + RangeArrays v0.3.2
  [c84ed2f1] + Ratios v0.4.5
  [c1ae055f] + RealDot v0.1.0
  [3cdcf5f2] + RecipesBase v1.3.4
  [01d81517] + RecipesPipeline v0.6.12
  [189a3867] + Reexport v1.2.2
  [42d2dcc6] + Referenceables v0.1.3
  [dee08c22] + RegionTrees v0.3.2
  [05181044] + RelocatableFolders v1.0.1
  [ae029012] + Requires v1.3.1
  [6038ab10] + Rotations v1.7.1
  [fdea26ae] + SIMD v3.7.1
  [94e857df] + SIMDTypes v0.1.0
  [476501e8] + SLEEFPirates v0.6.43
  [6c6a2e73] + Scratch v1.2.1
  [efcf1570] + Setfield v1.1.2
  [992d4aef] + Showoff v1.0.3
  [777ac1f9] + SimpleBufferStream v1.2.0
  [699a6c99] + SimpleTraits v0.9.4
  [47aef6b3] + SimpleWeightedGraphs v1.4.0
  [45858cf5] + Sixel v0.1.3
  [a2af1166] + SortingAlgorithms v1.2.1
  [276daf66] + SpecialFunctions v2.5.0
  [171d559e] + SplittablesBase v0.1.15
  [860ef19b] + StableRNGs v1.0.2
  [cae243ae] + StackViews v0.1.1
  [aedffcd0] + Static v0.8.9
  [0d7ed370] + StaticArrayInterface v1.6.0
  [90137ffa] + StaticArrays v1.9.13
  [1e83bf80] + StaticArraysCore v1.4.3
  [82ae8749] + StatsAPI v1.7.0
  [2913bbd2] + StatsBase v0.34.4
  [5e0ebb24] + Strided v2.2.0
  [4db3bf67] + StridedViews v0.3.2
  [3783bdb8] + TableTraits v1.0.1
  [bd369af6] + Tables v1.12.0
  [62fd8b95] + TensorCore v0.1.1
  [8290d209] + ThreadingUtilities v0.5.2
  [ac1d9e8a] + ThreadsX v0.1.12
  [731e570b] + TiffImages v0.11.3
  [06e1c1a7] + TiledIteration v0.5.0
  [a759f4b9] + TimerOutputs v0.5.25
  [3bb67fe8] + TranscodingStreams v0.11.3
  [28d57a85] + Transducers v0.4.84
  [410a4b4d] + Tricks v0.1.10
  [9d95972d] + TupleTools v1.6.0
  [5c2747f8] + URIs v1.5.1
  [3a884ed6] + UnPack v1.0.2
  [1cfade01] + UnicodeFun v0.4.1
  [1986cc42] + Unitful v1.22.0
  [45397f5d] + UnitfulLatexify v1.6.4
  [013be700] + UnsafeAtomics v0.2.1
  [d80eeb9a] + UnsafeAtomicsLLVM v0.1.5
  [41fe7b60] + Unzip v0.2.0
  [3d5dd08c] + VectorizationBase v0.21.71
  [e3aaa7dc] + WebP v0.1.3
  [efce3f68] + WoodburyMatrices v1.0.0
  [6e34b625] + Bzip2_jll v1.0.9+0
  [4ee394cb] + CUDA_Driver_jll v0.5.0+1
  [76a88914] + CUDA_Runtime_jll v0.6.0+0
  [83423d85] + Cairo_jll v1.18.2+1
  [ee1fde0b] + Dbus_jll v1.14.10+0
  [2702e6a9] + EpollShim_jll v0.0.20230411+1
  [2e619515] + Expat_jll v2.6.5+0
  [b22a6f82] + FFMPEG_jll v4.4.2+2
  [f5851436] + FFTW_jll v3.3.10+3
  [a3f928ae] + Fontconfig_jll v2.15.0+0
  [d7e528f0] + FreeType2_jll v2.13.3+1
  [559328eb] + FriBidi_jll v1.0.16+0
  [0656b61e] + GLFW_jll v3.4.0+2
  [d2c73de3] + GR_jll v0.72.8+0
  [78b55507] + Gettext_jll v0.21.0+0
  [61579ee1] + Ghostscript_jll v9.55.0+4
  [59f7168a] + Giflib_jll v5.2.3+0
  [7746bdde] + Glib_jll v2.82.4+0
  [3b182d85] + Graphite2_jll v1.3.14+1
  [2e76f6c2] + HarfBuzz_jll v8.5.0+0
  [c73af94c] + ImageMagick_jll v7.1.1+1
  [905a6f67] + Imath_jll v3.1.11+0
  [1d5cc7b8] + IntelOpenMP_jll v2025.0.4+0
  [aacddb02] + JpegTurbo_jll v3.1.1+0
  [c1c5ebd0] + LAME_jll v3.100.2+0
  [88015f11] + LERC_jll v3.0.0+1
  [dad2f222] + LLVMExtra_jll v0.0.23+0
  [1d63c593] + LLVMOpenMP_jll v18.1.7+0
  [dd4b983a] + LZO_jll v2.10.3+0
  [e9f186c6] + Libffi_jll v3.2.2+2
  [d4300ac3] + Libgcrypt_jll v1.11.0+0
  [7e76a0d4] + Libglvnd_jll v1.7.0+0
  [7add5ba3] + Libgpg_error_jll v1.51.1+0
  [94ce4f54] + Libiconv_jll v1.18.0+0
  [4b2f31a3] + Libmount_jll v2.40.3+0
  [89763e89] + Libtiff_jll v4.4.0+0
  [38a345b3] + Libuuid_jll v2.40.3+0
  [d3a379c0] + LittleCMS_jll v2.12.0+0
  [856f044c] + MKL_jll v2025.0.1+1
  [e7412a2a] + Ogg_jll v1.3.5+1
  [18a262bb] + OpenEXR_jll v3.2.4+0
  [643b3616] + OpenJpeg_jll v2.4.0+0
  [458c3c95] + OpenSSL_jll v1.1.23+1
  [efe28fd5] + OpenSpecFun_jll v0.5.6+0
  [91d4177d] + Opus_jll v1.3.3+0
  [36c8627f] + Pango_jll v1.56.1+0
  [30392449] + Pixman_jll v0.43.4+0
  [ea2cea3b] + Qt5Base_jll v5.15.3+2
  [a2964d1f] + Wayland_jll v1.21.0+2
  [2381bf8a] + Wayland_protocols_jll v1.36.0+0
  [02c8fc9c] + XML2_jll v2.13.6+1
  [aed1982a] + XSLT_jll v1.1.42+0
  [4f6342f7] + Xorg_libX11_jll v1.8.6+3
  [0c0b7dd1] + Xorg_libXau_jll v1.0.12+0
  [935fb764] + Xorg_libXcursor_jll v1.2.3+0
  [a3789734] + Xorg_libXdmcp_jll v1.1.5+0
  [1082639a] + Xorg_libXext_jll v1.3.6+3
  [d091e8ba] + Xorg_libXfixes_jll v6.0.0+0
  [a51aa0fd] + Xorg_libXi_jll v1.8.2+0
  [d1454406] + Xorg_libXinerama_jll v1.1.5+0
  [ec84b674] + Xorg_libXrandr_jll v1.5.4+0
  [ea2f1a96] + Xorg_libXrender_jll v0.9.11+1
  [14d82f49] + Xorg_libpthread_stubs_jll v0.1.2+0
  [c7cfdc94] + Xorg_libxcb_jll v1.17.0+3
  [cc61e674] + Xorg_libxkbfile_jll v1.1.2+1
  [12413925] + Xorg_xcb_util_image_jll v0.4.0+1
  [2def613f] + Xorg_xcb_util_jll v0.4.0+1
  [975044d2] + Xorg_xcb_util_keysyms_jll v0.4.0+1
  [0d47668e] + Xorg_xcb_util_renderutil_jll v0.3.9+1
  [c22f9ab0] + Xorg_xcb_util_wm_jll v0.4.1+1
  [35661453] + Xorg_xkbcomp_jll v1.4.6+1
  [33bec58e] + Xorg_xkeyboard_config_jll v2.39.0+0
  [c5fb5394] + Xorg_xtrans_jll v1.5.1+0
  [3161d3a3] + Zstd_jll v1.5.7+1
  [214eeab7] + fzf_jll v0.56.3+0
  [a4ae2306] + libaom_jll v3.11.0+0
  [0ac62f75] + libass_jll v0.15.2+0
  [1183f4f0] + libdecor_jll v0.2.2+0
  [f638f0a6] + libfdk_aac_jll v2.0.3+0
  [b53b4c65] + libpng_jll v1.6.47+0
  [075b6546] + libsixel_jll v1.10.5+0
  [f27f6e37] + libvorbis_jll v1.3.7+2
  [c5f90fcd] + libwebp_jll v1.4.0+0
  [1317d2d5] + oneTBB_jll v2022.0.0+0
  [1270edf5] + x264_jll v2021.5.5+0
  [dfaa095f] + x265_jll v3.5.0+0
  [d8fb68d0] + xkbcommon_jll v1.4.1+2
  [0dad84c5] + ArgTools
  [56f22d72] + Artifacts
  [2a0f44e3] + Base64
  [ade2ca70] + Dates
  [8bb1440f] + DelimitedFiles
  [8ba89e20] + Distributed
  [f43a241f] + Downloads
  [7b1f6079] + FileWatching
  [9fa8497b] + Future
  [b77e0a4c] + InteractiveUtils
  [4af54fe1] + LazyArtifacts
  [b27032c2] + LibCURL
  [76f85450] + LibGit2
  [8f399da3] + Libdl
  [37e2e46d] + LinearAlgebra
  [56ddb016] + Logging
  [d6f4376e] + Markdown
  [a63ad114] + Mmap
  [ca575930] + NetworkOptions
  [44cfe95a] + Pkg
  [de0858da] + Printf
  [3fa0cd96] + REPL
  [9a3f8284] + Random
  [ea8e919c] + SHA
  [9e88b42a] + Serialization
  [1a1011a3] + SharedArrays
  [6462fe0b] + Sockets
  [2f01184e] + SparseArrays
  [10745b16] + Statistics
  [4607b0f0] + SuiteSparse
  [fa267f1f] + TOML
  [a4e569a6] + Tar
  [8dfed614] + Test
  [cf7118a7] + UUIDs
  [4ec0a83e] + Unicode
  [e66e0078] + CompilerSupportLibraries_jll
  [deac9b47] + LibCURL_jll
  [29816b5a] + LibSSH2_jll
  [c8ffd9c3] + MbedTLS_jll
  [14a3606d] + MozillaCACerts_jll
  [4536629a] + OpenBLAS_jll
  [05823500] + OpenLibm_jll
  [efcefdf7] + PCRE2_jll
  [83775a58] + Zlib_jll
  [8e850b90] + libblastrampoline_jll
  [8e850ede] + nghttp2_jll
  [3f19e933] + p7zip_jll
Precompiling project...
PackageExtensionCompat
BFloat16s
TupleTools
CUDA_Runtime_Discovery
EnzymeCore
UnsafeAtomics
RandomNumbers
Atomix
CUDA_Driver_jll
Random123
LLVMExtra_jll
KernelAbstractions
LLVM
UnsafeAtomicsLLVM
CUDA_Runtime_jll
GPUArrays
GPUCompiler
CUDA
StridedViews
Strided
  20 dependencies successfully precompiled in 44 seconds (283 already precompiled)
63.6 s